using System;
using System.Windows.Forms;
using System.Drawing;
using System.Drawing.Imaging;
using System.Runtime.InteropServices;



namespace CUtil
{
	/// <summary>
	/// Summary description for GraphUtils.
	/// </summary>
	public class GraphUtils
	{
		public enum PrintOptions 
		{
			/// <summary><A HREF="ms-help://MS.VSCC/MS.MSDNVS/gdi/pantdraw_3qwk.htm">see Platform SDK</A></summary>
			PRF_CHECKVISIBLE  = 0x001,
			/// <summary><A HREF="ms-help://MS.VSCC/MS.MSDNVS/gdi/pantdraw_3qwk.htm">see Platform SDK</A></summary>
			PRF_NONCLIENT     = 0x002,
			/// <summary><A HREF="ms-help://MS.VSCC/MS.MSDNVS/gdi/pantdraw_3qwk.htm">see Platform SDK</A></summary>
			PRF_CLIENT        = 0x004,
			/// <summary><A HREF="ms-help://MS.VSCC/MS.MSDNVS/gdi/pantdraw_3qwk.htm">see Platform SDK</A></summary>
			PRF_ERASEBKGND    = 0x008,
			/// <summary><A HREF="ms-help://MS.VSCC/MS.MSDNVS/gdi/pantdraw_3qwk.htm">see Platform SDK</A></summary>
			PRF_CHILDREN      = 0x010,
			/// <summary><A HREF="ms-help://MS.VSCC/MS.MSDNVS/gdi/pantdraw_3qwk.htm">see Platform SDK</A></summary>
			PRF_OWNED         = 0x020
		}

		[System.Runtime.InteropServices.DllImportAttribute("gdi32.dll")]
		private static extern bool BitBlt(
			IntPtr hdcDest, // handle to destination DC
			int nXDest,  // x-coord of destination upper-left corner
			int nYDest,  // y-coord of destination upper-left corner
			int nWidth,  // width of destination rectangle
			int nHeight, // height of destination rectangle
			IntPtr hdcSrc,  // handle to source DC
			int nXSrc,   // x-coordinate of source upper-left corner
			int nYSrc,   // y-coordinate of source upper-left corner
			System.Int32 dwRop  // raster operation code
			);

		[System.Runtime.InteropServices.DllImportAttribute("gdi32.dll")]
		private static extern IntPtr  CreateDC(
			string lpszDriver,        // driver name
			string lpszDevice,        // device name
			string lpszOutput,        // not used; should be NULL
			IntPtr lpInitData	// optional printer data
			);


		/// <summary>SendMessage call.</summary>
		[DllImport("user32")]
		public static extern int SendMessage(IntPtr hWnd, WindowsMessages msg, IntPtr wParam, IntPtr lParam);

		/// <summary>SendMessage call.</summary>
		[DllImport("user32")]
		public static extern bool SendMessage(IntPtr hWnd, WindowsMessages msg, uint wParam, IntPtr lParam);

		/// <summary>
		/// Send Window message override to send strings
		/// </summary>
		[DllImport("User32.dll", CharSet=CharSet.Auto)]			
		public static extern IntPtr SendMessage(IntPtr hWnd, WindowsMessages msg, IntPtr wParam, string lParam);

		/// <summary>SendMessage overrride for direct integer values</summary>
		[DllImport("user32")]
		public static extern int SendMessage(IntPtr hWnd, WindowsMessages msg, int wParam, int lParam);

		public GraphUtils()
		{
			
		}
		public static Image ExtractBitmap(System.Windows.Forms.Control c)
		{
			
			Graphics g1 = c.CreateGraphics();
			Image myImage = new Bitmap(c.ClientRectangle.Width, c.ClientRectangle.Height, g1);
			Graphics g2 = Graphics.FromImage(myImage);
			IntPtr dc1 = g1.GetHdc();
			IntPtr dc2 = g2.GetHdc();
			BitBlt(dc2, 0, 0, c.ClientRectangle.Width, c.ClientRectangle.Height, dc1, 0, 0, 13369376);
			g1.ReleaseHdc(dc1);
			g2.ReleaseHdc(dc2);
			return myImage;
			
		}
		public static Image CropImage(Image myImage,int DelatX,int DeltaY)
		{
//			this.Left = 0;
//			this.Top = 0;
//			Bitmap theImage = new Bitmap(DeltaX, DeltaY);
//			Graphics g = Graphics.FromImage(myImage);
//			GraphicsUnit gu = GraphicsUnit.Pixel ;
//			Rectangle destRect = new Rectangle(0, 0, DeltaX, DeltaY);
//			//			g.TranslateTransform(-StartextPoint.X, -StartextPoint.Y);
//			if (firstCrop)
//			{
//				g.DrawImage(image, destRect, StartextPoint.X, StartextPoint.Y + 7, theImage.Width, theImage.Height + 20, GraphicsUnit.Pixel);
//				firstCrop = false;
//			}
//			else
//				g.DrawImage(image, destRect, StartextPoint.X, StartextPoint.Y, theImage.Width, theImage.Height, GraphicsUnit.Pixel);

			Image returnImage = (Bitmap)myImage.Clone();
			
//			this.SetBounds(0, 0, image.Width, image.Height + 50);
//			CroppingPaint = false;
//			SetupCropping();
//			Invalidate();

			return returnImage;
		}

		public virtual Bitmap ControlBitmap(Control controlParent,Control myControl)
		{
			return this.ControlBitmap(controlParent,myControl, new Size(myControl.Width, myControl.Height), null) ;		
		}
	
		public virtual Bitmap ControlBitmap(Control controlHolder, Control myControl, Size size, object val)
		{
	
			if (myControl != null)
			{
				Bitmap b = null;
				myControl.Size = size;
				System.Diagnostics.Debug.Assert(controlHolder != null);
				if (controlHolder != null)
				{
					b = GetBitmapFromControl(controlHolder, myControl);
				}
				return b;
			}
			
			return null;
		}
		public static Bitmap GetBitmapFromControl(Control controlHolder, Control c, bool isVisible)
		{
			Point origControlLoc = Point.Empty;
			if (isVisible == false)
			{
				
				if (c.Parent == null && controlHolder != null)
				{
					
					c.Location = new Point(-10000, -10000);
					controlHolder.Controls.Add(c);
				}
				else
				{
					
					origControlLoc = c.Location;
					c.Location = new Point(-10000, -10000);
					c.Visible = true;
				}
			}
			//Image extracting
			//prepare image and graphics.
			Bitmap b = null;
			if (c.Width > 0 && c.Height > 0 )
			{
				b = new Bitmap(c.Size.Width, c.Size.Height, System.Drawing.Imaging.PixelFormat.Format32bppArgb);

				Graphics g = Graphics.FromImage(b);
			
				IntPtr h = c.Handle;

				IntPtr phdc = g.GetHdc();

				SendMessage(h, WindowsMessages.WM_PRINT, phdc, 
					(IntPtr) (PrintOptions.PRF_CHILDREN
					| PrintOptions.PRF_CLIENT 
					| PrintOptions.PRF_NONCLIENT )
					);

				g.ReleaseHdc(phdc);

				//Recover the situation bevor extracting the image
				if (origControlLoc != Point.Empty)
				{
					c.Visible = false;
					c.Location = origControlLoc;
				}
				else if (controlHolder.Controls.Contains(c))
				{
					controlHolder.Controls.Remove(c);
				}
			}
			return b;
		}
		
		public static Bitmap GetBitmapFromControl(Control controlHolder, Control c)
		{
			//we suppose that the control is not visible, but created dynamically
			return GetBitmapFromControl(controlHolder, c, false);
		}
	
		public static void SetBitmapToControl(Control c, Bitmap b, int x, int y)
		{
			Graphics cg = c.CreateGraphics();
			cg.DrawImage(b, x, y, b.Size.Width, b.Size.Height);
		}
		
		public static void SetBitmapToControl(Control c, Bitmap b)
		{
			//we suppose, the image will be positioned top, left
			SetBitmapToControl( c, b, 0, 0);
		}
	
		public static void FitBitmapToForm(Form f, Bitmap b)
		{
			FitBitmapToControl((Control)f, b);
		}
	
		public static void FitBitmapToControl(Control c, Bitmap b)
		{
			Graphics cg = c.CreateGraphics();
			// Create rectangle for displaying image.
			Rectangle destRect = new Rectangle(0, 0, c.Width, c.Height);
			// Draw image to screen.
			cg.DrawImage(b, destRect);
			//free resources
			cg.Dispose();
			cg = null;
		}
	}
}
